package cn.siat.gene.service.impl;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.IdUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import cn.siat.common.core.constant.SecurityConstants;
import cn.siat.common.core.domain.R;
import cn.siat.common.core.exception.ServiceException;
import cn.siat.common.core.utils.DateUtils;
import cn.siat.common.core.web.domain.AjaxResult;
import cn.siat.common.security.utils.SecurityUtils;
import cn.siat.gene.domain.*;
import cn.siat.gene.mapper.*;
import cn.siat.gene.service.*;
import cn.siat.gene.domain.vo.ProgrammeVO;
import cn.siat.gene.domain.dto.ProgrammeQueryParam;
import cn.siat.gene.util.Assembler;
import cn.siat.system.api.RemoteNoticeService;
import cn.siat.system.api.RemoteUserService;
import cn.siat.system.api.domain.SysNotice;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import java.io.File;
import java.util.*;

/**
 * @Description: 方案信息
 * @Author: Administrator
 * @Date:   2022-10-22
 * @Version: V1.0
 */
@Service
public class ProgrammeServiceImpl extends ServiceImpl<ProgrammeMapper, Programme> implements IProgrammeService {


    @Autowired
    private IProgrammeStateService iProgrammeStateService;
    @Autowired
    private SequenceService sequenceService;
    @Autowired
    private SequenceOperateService sequenceOperateService;
    @Autowired
    private FeatureService featureService;
    @Autowired
    private IInformationService iInformationService;

    @Autowired
    private ProgrammeMapper programmeMapper;

    @Autowired
    private DesignTBProjectMainMapper projectMapper;
    @Autowired
    private IDesignTBProjectMainService designTBProjectMainService;

    @Autowired
    private RemoteUserService remoteUserService;

    @Autowired
    private RemoteNoticeService remoteNoticeService;

    @Autowired
    private DesignService designService;

    @Autowired
    SequenceMapper sequenceMapper;
    @Autowired
    SequenceOperateMapper sequenceOperateMapper;
    @Autowired
    FeatureMapper featureMapper;

    @Autowired
    TemplateMapper templateMapper;

    @Autowired
    private LogsService logsService;

    @Value("${path.sequence}")
    private String sequencePath;
    @Value("${path.template}")
    private String templatePath;

    /**
     *方案信息-分页列表查询
     *
     * @author zhanggj@hearglobal.com
     * @date 2022.10.31 15:47
     * @version 0.0.1
     */
    @Override
    public List<ProgrammeVO> queryPageList(ProgrammeQueryParam queryParams){
        String programmeName = queryParams.getProgrammeName();
        String projectId = queryParams.getProjectId();
        String userId = SecurityUtils.getUserId();
        if((projectId == null || !StringUtils.hasLength(projectId)) && !"1".equals(userId)){
            queryParams.setPossessStaff(userId);
        }
        if(StringUtils.hasLength(programmeName)){
            queryParams.setProgrammeName(programmeName.trim());
        }
        return programmeMapper.queryProgrammeList(queryParams);
    }


    /**
     * 通过模板创建方案
     * @param programme
     * @return
     */
    @Transactional
    @Override
    public Map<String,String>  createByTemplate(Programme programme) {
        //查看模板文件是否存在
        String separator = File.separator;
        Template template = templateMapper.selectById(programme.getTemplateId());
        if(template == null){
            throw new ServiceException("模板不存在!");
        }
        String templateFileName = template.getTemplateFileName();
        File templateFile = new File(this.templatePath + separator + templateFileName);
        if(!templateFile.exists()){
            throw new ServiceException("模板文件不存在!");
        }
        //先创建空白方案
        createBlank(programme);
        String programmeId = programme.getId();
        if(StringUtils.hasLength(programme.getProjectId())){
            logsService.saveLog(programme.getProjectId(),"新增","项目管理","design_t_b_project_main",
                    "将方案【" + programme.getProgrammeName() + "】添加到当前项目");
        }
        //复制模板文件到本地
        long fileSize = templateFile.length();
        File localFile = FileUtil.copy(templateFile,
                new File(sequencePath + separator + programmeId + separator + fileSize + "_" +templateFileName),
                true);
        Map<String,String> map = new HashMap();
        map.put("fileName", localFile.getName());
        map.put("programmeId", programmeId);
        return map;
    }

    /**
     * 新建空白方案
     * @param programme
     * @return
     */
    @Transactional
    @Override
    public AjaxResult createBlank(Programme programme) {
        programme.setProgrammeNumber(DateUtils.dateTimeNow());
        programme.setCreateTime(new Date());
        programme.setUpdateTime(new Date());
        programme.setCreateStaffNo(SecurityUtils.getUserId());
        programme.setPossessStaff(SecurityUtils.getUserId());
        programme.setCreateStaffName(SecurityUtils.getLoginUser().getSysUser().getNickName());
        programme.setPackState(1);
        programme.setPackState(1);
        // 获取未打包状态ID
        QueryWrapper queryWrapper = new QueryWrapper();
        queryWrapper.eq("programme_number", "FA_STATUS_001"); // 未打包标识
        ProgrammeState state = iProgrammeStateService.getOne(queryWrapper,false);
        if(state != null){
            programme.setStateId(state.getId());
        }
        boolean save = save(programme);
        if(!save){
            throw new ServiceException("方案添加失败...");
        }
        String projectId = programme.getProjectId();
        if(StringUtils.hasLength(projectId)){
            DesignTBProjectMain designTBProjectMain = designTBProjectMainService.selectDesignTBProjectMainById(projectId);
            if(designTBProjectMain == null  || designTBProjectMain.getProjectIsDelete() == 0){
                throw new ServiceException("选择项目不存在...");
            }
            designTBProjectMain.setProjectProgrammeNumber(designTBProjectMain.getProjectProgrammeNumber() + 1);
            designTBProjectMainService.updateById(designTBProjectMain);
            logsService.saveLog(programme.getProjectId(),"新增","项目管理","design_t_b_project_main",
                    "将方案【" + programme.getProgrammeName() + "】添加到当前项目");
        }
        return AjaxResult.success("操作成功",programme.getId());
    }

    /**
     * 方案信息-批量删除
     *
     * @author zhanggj@hearglobal.com
     * @date 2022.11.2 16:58
     * @version 0.0.1
     */
    @Override
    @Transactional
    public void deleteBatch(String ids){

        String projectId = "";
        DesignTBProjectMain designTBProjectMain = null;
        List<String> strings = Arrays.asList(ids.split(","));
        //删除方案表
        QueryWrapper<Programme> queryWrapperProgramme = new QueryWrapper<>();
        queryWrapperProgramme.in("id",strings);
        List<Programme> programmeList = this.list(queryWrapperProgramme);
        //在项目中移除方案
        for(Programme programme : programmeList){
            if(programme == null){
                throw new ServiceException("删除方案不存在！");
            }
            projectId = programme.getProjectId();
            if(StringUtils.hasLength(projectId)){
                designTBProjectMain = projectMapper.selectDesignTBProjectMainById(projectId);
                if(designTBProjectMain != null){
                    designTBProjectMain.setProjectProgrammeNumber(designTBProjectMain.getProjectProgrammeNumber() - 1);
                    logsService.saveLog(programme.getProjectId(),"移除","项目管理","design_t_b_project_main",
                            "将方案【" + programme.getProgrammeName() + "】从当前项目移除");
                }
            }
            //清理关联装置设计
            if(StringUtils.hasLength(programme.getDesignProjectId())){
                designService.clearDesign(programme.getId());
            }
        }
        removeByIds(strings);
        //删除本地gbff文件,以及sequence表,sequenceOperate表,feature表对应数据
        for (String programmeId : strings) {
            //删本地gbff文件夹
            String localFilePath = sequencePath + java.io.File.separator + programmeId;
            java.io.File file = new java.io.File(localFilePath);
            FileUtil.del(file);
            //获取序列表id
            List<Sequence> sequenceList = sequenceMapper.list(new Sequence().setProgrammeId(programmeId));
            if(!sequenceList.isEmpty()){
                List<Long> sequenceIds = new ArrayList<>();
                for (Sequence sequence : sequenceList) {
                    sequenceIds.add(sequence.getId());
                }
                sequenceService.removeByIdList(sequenceIds);
                sequenceOperateService.removeBySequenceIdList(sequenceIds);
                featureService.removeBySequenceIdList(sequenceIds,null);
            }


        }

        //删除历史表

        //删除文件表
    }

    /**
     * 克隆方案
     */
    @Override
    @Transactional
    public void cloneProgramme(Programme programme){
        String oldId = programme.getId();
        Programme oldProgramme = programmeMapper.selectById(oldId);
        if(oldProgramme == null){
            throw new ServiceException("被克隆方案不存在...");
        }
        String userId = SecurityUtils.getUserId();
        Date date = new Date();
        //复制方案表
        String newId = IdUtil.getSnowflakeNextIdStr();
        String sourceFileMergeName = oldProgramme.getSourceFileMergeName();
        oldProgramme.setProgrammeState(1);
        oldProgramme.setId(newId);
        oldProgramme.setProgrammeName(programme.getProgrammeName());
        //克隆后的方案所属人和创建人均为当前用户
        oldProgramme.setPossessStaff(userId);
        oldProgramme.setCreateStaffNo(userId);
        oldProgramme.setCreateStaffName(SecurityUtils.getLoginUser().getSysUser().getNickName());
        oldProgramme.setCreateTime(date);
        //将方案打包状态更改为未打包
        oldProgramme.setPackState(1);
        oldProgramme.setProjectId(null);
        //判断原方案是否有所属项目
        /*if(StringUtils.hasLength(programme.getProjectId())){
            DesignTBProjectMain designTBProjectMain = projectMapper.selectById(oldProgramme.getProjectId());
            if (designTBProjectMain == null || designTBProjectMain.getProjectIsDelete() == 0) {
                throw new ServiceException("原方案所属项目不存在...");
            }
            logsService.saveLog(oldProgramme.getProjectId(),"克隆","项目","design_t_b_project_main",
                    "克隆方案【" + programme.getProgrammeName() + "】至当前项目");
        }*/
        this.save(oldProgramme);
        FileUtil.copyContent(new File(this.getSequenceFolderPath(oldId)),
                new File(this.getSequenceFolderPath(newId)), true);
        //复制序列表
        this.copy(oldId,newId);
    }

    /**
     * 修改后的方案分享，不需要被分享人确认
     */
    @Override
    @Transactional

    public void share(Programme programme) {
        //获取被分享的方案
        String programmeId = programme.getId();
        Date date = new Date();
        //校验参数合法
        Integer programmeState = programme.getProgrammeState();
        String possessStaff = programme.getPossessStaff();
        if(StringUtils.hasLength(programmeId) && programmeState == null && StringUtils.hasLength(possessStaff)){
            throw new ServiceException("有参数为空");
        }
        Programme one = programmeMapper.selectById(programmeId);
        String newName = (one.getProgrammeName() + "_copy");
        //被分享的方案命名
        if(one.getProgrammeName().length() > 24){
            newName = one.getProgrammeName().substring(0,24) + "_copy";
        }
        QueryWrapper wrapper = new QueryWrapper();
        wrapper.eq("possess_staff", possessStaff);
        wrapper.like("programme_name",newName);
        Long count = programmeMapper.selectCount(wrapper);
        if(one == null){
            throw new ServiceException("被分享方案不存在...");
        }
        //复制方案表
        String snowflakeNextIdStr = IdUtil.getSnowflakeNextIdStr();
        String sourceFileMergeName = one.getSourceFileMergeName();
        one.setId(snowflakeNextIdStr);
        one.setProgrammeName(newName + count);
        one.setProgrammeState(programmeState);
        one.setPossessStaff(possessStaff);
        one.setCreateTime(date);
        one.setProjectId("");
        //如果分享时选择的可操作权限非仅下载，将方案打包状态更改为未打包
        if(programmeState != 2){
            one.setPackState(1);
        }else{
            one.setPackFileName(programme.getPackFileName());
        }
        this.save(one);
        FileUtil.copyContent(new File(this.getSequenceFolderPath(programmeId)),
                new File(this.getSequenceFolderPath(snowflakeNextIdStr)), true);
        //复制序列表
        if(one.getPackType().contains("2")){
            this.copy(programmeId , snowflakeNextIdStr);
        }

        //向被分享用户发送消息
        SysNotice notice = new SysNotice();
        notice.genId();
        notice.setNoticeTitle("分享方案");
        notice.setNoticeType("1");
        notice.setStatus("1");
        notice.setNoticeContent(SecurityUtils.getLoginUser().getSysUser().getNickName() +
                "将方案 " + programme.getProgrammeName() + " 分享给您，分享后的方案名称为 " + newName + count );
        ArrayList<String> list = new ArrayList<>();
        list.add(possessStaff);
        notice.setUserIdList(list);
        remoteNoticeService.send(notice,SecurityConstants.INNER);
    }

    /**
     * 分享方案
     *
     * @author zhanggj@hearglobal.com
     * @date 2022.11.2 16:58
     * @version 0.0.1
     */
    @Override
    public String shareProgramme(Programme programme){
        String programmeId = programme.getId();
        Programme programme1 = programmeMapper.selectById(programmeId);
        if(programme1 == null){
            throw new ServiceException("被分享方案不存在...");
        }
        Integer programmeState1 = programme.getProgrammeState();
        String possessStaff = programme.getPossessStaff();
        if(StringUtils.hasLength(programmeId) && programmeState1 == null && StringUtils.hasLength(possessStaff)){
            throw new ServiceException("有参数为空");
        }
//        String userid = remoteUserService.getUserInfo(possessStaff, SecurityConstants.INNER).getData().getUserid();
        //给被分享人发送消息通知
        SysNotice notice = new SysNotice();
        notice.genId();
        notice.setNoticeTitle("分享方案");
        notice.setNoticeType("3");
        notice.setStatus("0");
        notice.setNoticeContent(SecurityUtils.getLoginUser().getSysUser().getNickName() +
                "将方案 " + programme.getProgrammeName() + " 分享给您");
        ArrayList<String> list = new ArrayList<>();
        list.add(possessStaff);
        notice.setUserIdList(list);
        remoteNoticeService.send(notice,SecurityConstants.INNER);

        String username = SecurityUtils.getUserId();
        Date date = new Date();
        Information information = new Information();
        Assembler.assemble(programme,information);
        information.setPackFileName(programme1.getPackFileName());
        information.setPackType(programme1.getPackType());
        information.setInformationState(0);
        information.setId(notice.getNoticeId());
        information.setProgrammeId(programmeId);
        information.setCreateStaffNo(username);
        information.setCreateTime(date);
        iInformationService.save(information);
        return "1";
    }

    /**
     * 获取处理分享方案
     *
     * @author zhanggj@hearglobal.com
     * @date 2022.11.2 15:41
     * @version 0.0.1
     */
    @Override
    public List<Information> getDisposeShareProgramme(){
        QueryWrapper<Information> queryWrapper = new QueryWrapper<>();
//        queryWrapper.eq("possess_staff", SecurityUtils.getUserId()).eq("information_state", "0");
        HashMap<String ,Object> ss = new HashMap<String ,Object>(10);
        ss.put("possess_staff", SecurityUtils.getUserId());
//        ss.put("possess_staff", "1588457461390180352");
        ss.put("information_state", 0);

        queryWrapper.allEq(ss);
        List<Information> list = iInformationService.list(queryWrapper);
        return list;
    }

    /**
     * 项目中移除方案
     * @param id 方案id
     * @return
     */
    @Override
    @Transactional
    public int removeProgrammeInProjectById(String id) {
        Programme programme = programmeMapper.selectById(id);
        if(programme == null){
            throw new ServiceException("该方案不存在...");
        }
        String projectId = programme.getProjectId();
        programme.setProjectId("");
        int i = programmeMapper.updateById(programme);
        if(i <= 0 || i > 1){
            throw new ServiceException("移除方案失败...");
        }
        DesignTBProjectMain designTBProjectMain = projectMapper.selectById(projectId);
        if(designTBProjectMain == null){
            throw new ServiceException("项目不存在...");
        }
        designTBProjectMain.setProjectProgrammeNumber(designTBProjectMain.getProjectProgrammeNumber() - 1);
        logsService.saveLog(projectId,"移除","项目管理","design_t_b_project_main",
                "将方案【" + programme.getProgrammeName() + "】从当前项目移除");
        return projectMapper.updateById(designTBProjectMain);
    }

    @Override
    public List<Map<String, String>> getAllUser() {
//        String userId = SecurityUtils.getUserId();
//        String[] arr = {userId};
//        R<List<Map<String, String>>> r = remoteUserService.infoNotINProject(arr,SecurityConstants.INNER);

        String[] roles = new String[]{"gene_general","gene_admin"};
        R<List<Map<String, String>>> list = remoteUserService.listExaminer(roles, SecurityConstants.INNER);
        return list.getData();
    }

    //获取最近浏览10条方案
    @Override
    public List<Programme> selectViewedProgrammes() {
        String username = SecurityUtils.getUserId();
        QueryWrapper<Programme> queryWrapper = new QueryWrapper<>();
        queryWrapper.select("programme_name","viewed_time","id");
        queryWrapper.eq("create_staff_no", username);
        queryWrapper.isNotNull("viewed_time");
        queryWrapper.orderByDesc("viewed_time");
        queryWrapper.last("limit 10");
        List<Programme> programmeList = programmeMapper.selectList(queryWrapper);
        return programmeList;
    }

    @Override
    public Boolean checkName(String programmeName,String id) {
        QueryWrapper<Programme> wrapper = new QueryWrapper<Programme>()
                .eq("programme_name", programmeName)
                .eq("create_staff_no", SecurityUtils.getUserId());
        //编辑弹窗不校验本身
        if(id!=null){
            wrapper.ne("id", id);
        }
        Long count = programmeMapper.selectCount(wrapper);
        if(count == null || count == 0L){
            return  false;
        }
        return true;
    }


    public Map<String,String> shareProgramme2(Programme programme){
        String programmeId = programme.getId();
        Integer programmeState1 = programme.getProgrammeState();
        String possessStaff = programme.getPossessStaff();
        if(programmeId == null && programmeState1 == null && possessStaff == null){
            throw new ServiceException("分享失败！！");
        }
        String username = SecurityUtils.getUserId();
        Date date = new Date();

        //复制方案表
        QueryWrapper<Programme> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("id", programmeId);
        Programme one = this.getOne(queryWrapper, false);
        if(one == null){
            throw new ServiceException("被分享方案不存在！!");
        }
        String snowflakeNextIdStr = IdUtil.getSnowflakeNextIdStr();
        String sourceFileMergeName = one.getSourceFileMergeName();
        one.setId(snowflakeNextIdStr);
        one.setProgrammeName(programme.getProgrammeName());
        one.setProgrammeState(programmeState1);
        one.setPossessStaff(possessStaff);
        one.setCreateStaffNo(username);
        one.setCreateTime(date);
        one.setProjectId("");
        //如果分享时选择的可操作权限非仅下载，将方案打包状态更改为未打包
        if(programmeState1 != 2){
            one.setPackState(1);
        }else{
            one.setPackFileName(programme.getPackFileName());
        }
//        one.setSourceFileMergeName(snowflakeNextIdStr + "_source.gbff");
        this.save(one);
        String separator = File.separator;
        File copy = FileUtil.copy(new File(sequencePath + separator + programmeId + separator + sourceFileMergeName),
                new File(sequencePath + separator + snowflakeNextIdStr + separator + one.getSourceFileMergeName()), true);
        Map<String,String> map = new HashMap();
        map.put("fileName", copy.getName());
        map.put("programmeId", snowflakeNextIdStr);

        //复制操作历史表
        if(one.getPackType().contains("2")){
            List<Sequence> sequenceList = sequenceMapper.list(new Sequence().setProgrammeId(programmeId));
            if(!sequenceList.isEmpty()){
                List<Long> sequenceIds = new ArrayList<>();
                for (Sequence sequence : sequenceList) {
                    sequenceIds.add(sequence.getId());
                }
                sequenceService.removeByIdList(sequenceIds);
                sequenceOperateService.removeBySequenceIdList(sequenceIds);
                featureService.removeBySequenceIdList(sequenceIds,null);
            }
        }
        //复制方案状态表
        return map;
    }

    @Override
    public Map<String,String> disposeShareProgramme(String id, Integer informationState, String newProgrammeName){
        QueryWrapper<Information> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("id", id);
        Information one = iInformationService.getOne(queryWrapper, false);
        if(one == null){
            throw new ServiceException("消息唯一标识，数据未找到");
        }
        one.setInformationState(informationState);
        iInformationService.updateById(one);

        if(informationState == 2){
            Programme programme = new Programme();
            Assembler.assemble(one,programme);
            programme.setId(one.getProgrammeId());
            programme.setProgrammeName(newProgrammeName);
            return shareProgramme2(programme);
        }
        return null;
    }

    /**
     *复制文件表
     *
     * @author zhanggj@hearglobal.com
     * @date 2022.11.2 16:52
     * @version 0.0.1
     */
    private String copyFile(String packFileId) {
        return null;
    }


    @Override
    public List<ProgrammeVO> listNoProjectProgrammes(String projectId) {
        Programme programme = new Programme().setProjectId(projectId).
                setCreateStaffNo(SecurityUtils.getLoginUser().getUserid());
        return programmeMapper.listNoProjectProgrammes(programme);
    }

    @Override
    public AjaxResult updateProject(String[] ids, String projectId, String projectName) {
        for(String id : ids){
            Programme programme = programmeMapper.selectById(id);
            if(programme == null){
                throw new ServiceException("添加方案不存在");
            }
            String oldProjectId = programme.getProjectId();
            String programmeName = programme.getProgrammeName();
            String oldProjectName = "";
            if(StringUtils.hasLength(oldProjectId)){
                oldProjectName  = projectMapper.selectById(oldProjectId).getProjectName();
            }
            programme.setProjectId(projectId);
            int i = programmeMapper.updateById(programme);
            if(i < 1){
                throw new ServiceException("操作失败！");
            }
            if(StringUtils.hasLength(oldProjectName)){
                logsService.saveLog(oldProjectId,"移除","项目","design_t_b_project_main",
                        "将方案【" + programmeName + "】从当前项目移除，添加至项目【" + projectName + "】");
                logsService.saveLog(projectId,"新增","项目","design_t_b_project_main",
                        "将方案【" + programmeName + "】从项目【"+ oldProjectName +"】移动到当前项目");
            }else{
                logsService.saveLog(projectId,"新增","项目","design_t_b_project_main",
                        "将方案【" + programmeName + "】添加到当前项目");
            }
        }
        return AjaxResult.success();
    }

    @Override
    public void toLab(Map<String, String> params) {
        String programmeId = params.get("programmeId");
        Programme programme = programmeMapper.selectById(programmeId);
        System.err.println("params:"+params);
        SysNotice sysNotice= new SysNotice();
        String title = "已通过云实验室审核";
        sysNotice.setNoticeTitle(title);
        String content = "您的方案名为《"+programme.getProgrammeName()+"》的方案已通过云实验室审核!";
        sysNotice.setNoticeContent(content);
        sysNotice.setUserIdList(Arrays.asList(programme.getCreateStaffNo()));
        remoteNoticeService.send(sysNotice, SecurityConstants.INNER);
    }

    @Override
    public void editProgramme(Programme programme) {
        String projectId = programme.getProjectId();
        DesignTBProjectMain projectMain = null;
        Programme oldProgramme = programmeMapper.selectById(programme.getId());
        String programmeName = programme.getProgrammeName();
        String oldProjectId = oldProgramme.getProjectId();
        //修改后的方案有所属项目 且与原方案所属项目不同
        if(StringUtils.hasLength(projectId) && (!projectId.equals(oldProjectId))){
            projectMain = projectMapper.selectDesignTBProjectMainById(projectId);
            //原方案无所属项目
            if(projectMain != null && !StringUtils.hasLength(oldProjectId)){
                logsService.saveLog(projectId,"新增","项目","design_t_b_project_main",
                        "将方案【" + programmeName + "】添加到当前项目");
            //原方案有所属项目
            }else if(projectMain != null && StringUtils.hasLength(oldProjectId)){
                logsService.saveLog(oldProjectId,"移除","项目","design_t_b_project_main",
                        "将方案【" + programmeName + "】从当前项目移动至项目【"+ projectMain.getProjectName() + "】");
                logsService.saveLog(projectId,"新增","项目","design_t_b_project_main",
                        "将方案【" + programmeName + "】添加到当前项目");
            }
            //修改后的方案无所属项目
        }else if(!StringUtils.hasLength(projectId) && StringUtils.hasLength(programmeName)){
            if(StringUtils.hasLength(oldProjectId)){
                logsService.saveLog(oldProjectId,"移除","项目","design_t_b_project_main",
                        "将方案【" + programmeName + "】从当前项目中移除");
            }
        }
        if(projectId == null  && StringUtils.hasLength(programmeName)){
            programme.setProjectId("");
        }
        programme.setUpdateStaffNo(SecurityUtils.getUserId());
        programme.setUpdateTime(new Date());
        programmeMapper.updateById(programme);
    }

    @Override
    public List<Map<String, String>> selectProgrammeCreateStaffList() {
        String possessStaff = null;
        String userid = SecurityUtils.getLoginUser().getUserid();
        if(!"1".equals(userid)){
            possessStaff = userid;
        }
        return programmeMapper.selectProgrammeCreateStaffList(possessStaff);
    }

    @Override
    public AjaxResult updateExamineState(Programme programme) {
        programmeMapper.updateExamineState(programme);
        return null;
    }

    @Override
    public boolean existById(String id) {
        int count = programmeMapper.existById(id);
        return count > 0;

    }

    private String getSequenceFolderPath(String programmeId){
        return sequencePath +"/"+programmeId+"/";
    }

    private void copy(String oldId, String newId){
        List<Sequence> sequenceList = sequenceMapper.list(new Sequence().setProgrammeId(oldId));
        if(!sequenceList.isEmpty()){
            for (Sequence sequence : sequenceList) {
                Long id = sequence.getId();
                sequence.setId(null).setProgrammeId(newId);
                sequenceMapper.save(sequence);
                //复制序列操作表
                List<SequenceOperate> list = sequenceOperateMapper.list(new SequenceOperate().setSequenceId(id));
                //记录新旧ID对应关系，后面Feature表的History字段复制需要用到
                List<Long> oldOperateIds = new ArrayList<>();
                List<Long> newOperateIds = new ArrayList<>();
                Map<Long,Long> operateIds = new HashMap<>();
                if(!list.isEmpty()){
                    for (SequenceOperate operate : list) {
                        oldOperateIds.add(operate.getId());
                        operate.setId(null).setSequenceId(sequence.getId());
                    }
                    Collections.reverse(list);
                    sequenceOperateMapper.saveList(list);
                    list = sequenceOperateMapper.list(new SequenceOperate().setSequenceId(sequence.getId()));
                    for (SequenceOperate operate : list) {
                        newOperateIds.add(operate.getId());
                    }
                    Long[] oldIds = new Long[oldOperateIds.size()];
                    Long[] newIds = new Long[newOperateIds.size()];
                    oldIds = oldOperateIds.toArray(oldIds);
                    Arrays.sort(oldIds);
                    newIds = newOperateIds.toArray(newIds);
                    Arrays.sort(newIds);
                    for (int i = 0; i < oldIds.length; i++) {
                        operateIds.put(oldIds[i],newIds[i]);
                    }
                }
                //复制Feature表
                List<Feature> saveFeatures = new ArrayList<>(2000);
                List<Feature> fList = featureMapper.listBySequenceId(id);
                if(!fList.isEmpty()){
                    for(Feature feature : fList){
                        Map<String, String> history = feature.getHistory();
                        Map<String,String> map = new HashMap<>();
                        if (history == null) {
                            history = new HashMap<>();
                        }else{
                            //遍历上面保存新旧操作ID的Map，修改History
                            for(Long key : operateIds.keySet()){
                                if(history.containsKey(key.toString())){
                                    String value = history.get(key.toString());
                                    map.put(operateIds.get(key).toString(),value);
                                }
                            }
                        }
                        feature.setHistory(map);
                        feature.setSequenceId(sequence.getId());
                        saveFeatures.add(feature);
                        if(saveFeatures.size()==2000){
                            //2k插入一次
                            featureMapper.saveCloneList(saveFeatures);
                            saveFeatures.clear();
                        }
                    }
                    if(!saveFeatures.isEmpty()){
                        featureMapper.saveCloneList(saveFeatures);
                        saveFeatures.clear();
                    }
                }
            }
        }
    }
}
